import asyncio
import itertools, string
from tqdm import tqdm


async def run(pwd):
    pwd = "".join(pwd)
    print(f"尝试：{pwd}")
    #if pwd == 'ehrtnjc5':
    if pwd == '1bAf':
        print(f"密码是：{pwd}")
        raise Exception("任务完成,中止程序")  # 当number等于5时抛出异常中止程序


async def main():
    try:
        # 假设你有一个迭代器 iterator
        concurrent_num = 200
        password_length = 4
        # password_types = ['ascii_letters', 'digits', 'punctuation']
        password_types = ['ascii_letters', 'digits']
        characters = "".join([getattr(string, k) for k in password_types])
        # string.ascii_letters + string.digits + string.punctuation
        print(characters)
        password_combinations = itertools.product(characters, repeat=password_length)
        # 创建协程列表
        coroutines = [run(pwd) for pwd in password_combinations]
        # coroutines = [run(pwd) for pwd in tqdm(password_combinations, total=len(characters) ** password_length, desc="Processing", ncols=100, ascii=True)]
        # print(len(coroutines), len(characters) ** password_length)
        # 创建协程池的大小
        semaphore = asyncio.Semaphore(concurrent_num)
        # 在协程池中运行所有协程
        results = await asyncio.wait([asyncio.shield(semaphore.acquire())])
        await asyncio.gather(*coroutines)
        semaphore.release()

    except KeyboardInterrupt:
        print("强制中止...")
    except Exception as e:
        print(e)
    finally:
        print("退出主进程")


if __name__ == "__main__":
    # 运行事件循环
    asyncio.run(main())